package com.wzf.greattruth.zookeeper.lock.watcher;

import org.apache.zookeeper.WatchedEvent;
import org.apache.zookeeper.Watcher;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.wzf.greattruth.zookeeper.lock.DistributedWaitLock;

/**
 * 如果希望实现串行锁，那么可以使用此Watcher，此锁的逻辑如下
 * <li>根据在zookeeper创建node的顺序，注册监听器,监听上一个Node删除事件
 * <li>上一个线程释放锁以后，此watcher会检查当前是不是最小的node，如果是，那么认为上锁成功
 * 
 * @author wuzhengfei
 *
 */
public abstract class DistributedWaitLockWatcher<T> implements Watcher {
    private static final Logger LOGGER = LoggerFactory.getLogger(DistributedWaitLockWatcher.class);

    private DistributedWaitLock locker;

    private T t;

    /**
     * 获取锁以后的回调函数
     * 
     * @param obj
     */
    public abstract void callbackWhenGainLock(WatchedEvent event, T obj);

    @Override
    public void process(WatchedEvent event) {
        // 收到监控事件以后，重新尝试上锁
        if (locker != null) {
            boolean lock = locker.lock();
            // 上锁成功以后执行回调函数
            if (lock) {
                try {
                    callbackWhenGainLock(event, t);
                } finally {
                    locker.unlock();
                }
            }
        }
    }

    public void setZooKeeperDistributeLock(DistributedWaitLock waitLock) {
        this.locker = waitLock;
    }

    public T getT() {
        return t;
    }

    public void setT(T t) {
        this.t = t;
    }

}